package cc.linker.steplink.crm.controller;

import cc.linker.steplink.crm.commons.BeanMapUtils;
import cc.linker.steplink.crm.commons.Constants;
import cc.linker.steplink.crm.commons.model.PcUserInfo;
import cc.linker.steplink.crm.commons.utils.CreateListStrUtil;
import cc.linker.steplink.crm.dao.PreciseDao;
import cc.linker.steplink.crm.domain.AuthorTask;
import cc.linker.steplink.crm.domain.Precise;
import cc.linker.steplink.crm.merchant.dao.PersonnelDao;
import cc.linker.steplink.crm.merchant.pojo.PersonGroupDTO;
import cc.linker.steplink.crm.merchant.service.PersonnelService;
import cc.linker.steplink.crm.merchanth5.commons.UserInfoUtil;
import cc.linker.steplink.crm.merchanth5.service.acs.DynamicService;
import cc.linker.steplink.crm.response.GlobalException;
import cc.linker.steplink.crm.response.ResponseException;
import cc.linker.steplink.crm.service.IPreciseService;
import cc.linker.steplink.crm.service.ISysConfig;
import cc.linker.steplink.crm.task.PrecisionPush;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.mongodb.util.JSON;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.*;
import java.util.concurrent.ExecutionException;

@RestController
@RequestMapping("/precise")
public class PreciseController {


    @Autowired
    private IPreciseService preciseService;

    @Autowired
    private ISysConfig sysConfig;

    @Autowired
    private DynamicService dynamicService;
    @Autowired
    private UserInfoUtil userInfoUtil;

    @Autowired
    private PersonnelDao personnelDao;

    @Autowired
    private PersonnelService personnelService;


    @Autowired
    private PrecisionPush precisionPush;
    @Autowired
    private PreciseDao preciseDao;


    /*
     * 精准推送列表
     */
    @GetMapping("/list")
    public Object list(
            HttpServletRequest request,
            @RequestParam(value = "pageIndex", defaultValue = "1", required = false) int pageIndex,
            @RequestParam(value = "pageSize", defaultValue = "10", required = false) int pageSize)
            throws Exception {
        // 查询用户信息
        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);
        Map<String, Object> preciseMap = new HashMap<String, Object>();
        String orgId = userinfo.getOrgId();
        preciseMap.put("orgId", orgId);

        PageHelper.startPage(pageIndex, pageSize);
        PageInfo<Map<String, Object>> mapPageInfo = new PageInfo<>(preciseService.listPrecise(preciseMap));

        return mapPageInfo;
    }

    /**
     * 获取单个计划详情
     *
     * @param taskId
     * @return
     * @throws Exception
     */
    @GetMapping("/get")
    public Object get(String taskId) throws Exception {
        return preciseService.getPrecise(taskId);
    }

    @PostMapping("/addwxpush")
    public boolean addWxPush(HttpServletRequest request, @RequestBody Map<String, Object> map) throws Exception {
        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);
        String orgId = userinfo.getOrgId();
        String adminId = userinfo.getAdminId();
        Map content = (Map) map.get("content");
        if (null == content || content.size() == 0) {
            throw GlobalException.build("至少选择一篇");
        }
        Integer wxCount = sysConfig.getWxCountByOrgId(orgId);
        if (wxCount < 1) {
            throw GlobalException.build("请先绑定公众号");
        }
        Map<String, Object> param = new HashMap<>();
        param.put("content", JSON.serialize(content));
        param.put("orgId", orgId);
        param.put("sendTime", map.get("sendTime"));
        param.put("taskName", map.get("taskName"));
        param.put("groupId", map.get("groupId"));
        param.put("createUserId", adminId);
        param.put("taskId", UUID.randomUUID().toString());
        dynamicService.recording(request, 11, "创建" + map.get("taskName"));
        return preciseService.addWxPrecise(param);
    }

    @PostMapping("/updatewxpush")
    public boolean updateWxPush(HttpServletRequest request, @RequestBody Map<String, Object> map) throws Exception {
        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);
        String orgId = userinfo.getOrgId();
        Map content = (Map) map.get("content");
        Integer wxCount = sysConfig.getWxCountByOrgId(orgId);
        if (wxCount < 1) {
            throw GlobalException.build("请先绑定公众号");
        }
        if (StringUtils.isEmpty(map.get("taskId"))) {
            throw GlobalException.build("参数错误");
        }
        Map<String, Object> param = new HashMap<>();
        param.put("content", JSON.serialize(content));
        param.put("taskId", map.get("taskId"));
        param.put("sendTime", map.get("sendTime"));
        param.put("taskName", map.get("taskName"));
        param.put("groupId", map.get("groupId"));
        return preciseService.updateWxPush(param);
    }

    @GetMapping("/getinfo")
    public Map getInfo(HttpServletRequest request, @RequestParam(value = "taskId", defaultValue = "") String taskId) {
        if (StringUtils.isEmpty(taskId)) {
            throw GlobalException.build("参数错误");
        }
        return preciseService.getInfo(taskId);
    }

    /*
     * 添加计划  type content
     */
    @PostMapping("/add")
    public void add(HttpServletRequest request, @RequestBody Map<String, Object> map) throws Exception {
        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);
        String adminId = userinfo.getAdminId();

        //机构用户id
        map.put("createUserId", adminId);

        //机构码
        String orgId = userinfo.getOrgId();

        map.put("orgId", orgId);
        Integer wxCount = sysConfig.getWxCountByOrgId(orgId);
        if (wxCount < 1) {
            throw new GlobalException(new ResponseException(400, "请先绑定公众号"));
        }
        Map content = (Map) map.get("content");
        map.put("content", JSON.serialize(content));
        Precise precise = BeanMapUtils.mapToBean(map, Precise.class);
        preciseService.addPrecise(precise);
        dynamicService.recording(request, 11, "创建" + precise.getTaskName());
    }

    /**
     * 更新计划
     */
    @PostMapping("/update")
    public void update(HttpServletRequest request, @RequestBody Map<String, Object> map) throws Exception {
        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);

        String adminId = userinfo.getAdminId();
        map.put("createUserId", adminId);
        String orgId = userinfo.getOrgId();
        map.put("orgId", orgId);
        Integer wxCount = sysConfig.getWxCountByOrgId(orgId);
        if (wxCount < 1) {
            throw new GlobalException(new ResponseException(400, "请先绑定公众号"));
        }
        Map content = (Map) map.get("content");
        map.put("content", JSON.serialize(content));
        Precise precise = BeanMapUtils.mapToBean(map, Precise.class);
        preciseService.updatePrecise(precise);

    }


    /**
     * 删除任务
     */
    @PostMapping("/del")
    public void del(@RequestBody Map<String, Object> map, HttpServletRequest request) throws Exception {
        String taskId = (String) map.get("taskId");
        Map<String, Object> info = preciseService.getInfo(taskId);
        preciseService.delPrecise(taskId);
        dynamicService.recording(request, 12, "关闭" + info.get("taskName"));
    }

    /**
     * 获取发送结果
     *
     * @param taskId
     * @return
     */
    @GetMapping("getsendreport")
    public Map<String, Object> getSendReport(@RequestParam String taskId) {
        if (StringUtils.isEmpty(taskId)) {
            throw GlobalException.build("参数错误");
        }
        return preciseService.getSendReport(taskId);
    }

    /**
     * test email api You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'PUSH_TYPE )
     *
     * @return
     */
    @GetMapping("email")
    @Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRED)
    public String email() {
        // 获取待推送列表 taskId, groupId, content, pushType 1-智能推送 2-自定义推送, orgId
        List<Map<String, Object>> toBePushedList = preciseDao.getToBePushedList();
        precisionPush.type1(toBePushedList);
        return "email test";
    }


    /**
     * 【千人计划】 - 发送邮件 原先
     * emails   邮件列表
     * content  邮件内容
     * taskName 邮件主题
     **/
    @PostMapping("/sendEmailToPersonnel")
    public void sendEmailToPersonnel(HttpServletRequest request,
                                     @RequestBody Map<String, Object> map) throws Exception {

        PcUserInfo userinfo = this.userInfoUtil.getPcUserInfo(request);
        String adminId = userinfo.getAdminId();
        String taskId = UUID.randomUUID().toString();
        String orgId = userinfo.getOrgId();

        //机构码
        map.put("orgId", orgId);
        map.put("taskId", taskId);
        personnelService.sendEmailToPesonnal(map, null);

        map.put("orgId", orgId);
        Integer wxCount = sysConfig.getWxCountByOrgId(orgId);
        if (wxCount < 1) {
            throw new GlobalException(new ResponseException(400, "请先绑定公众号"));
        }
        Map content = (Map) map.get("content");
        map.put("content", JSON.serialize(content));

        Precise precise = BeanMapUtils.mapToBean(map, Precise.class);
        //机构用户id
        precise.setCreateUserId(adminId);

        //任务id
        precise.setTaskId(taskId);
        precise.setStatus("1");
        precise.setType("email");

        preciseService.addPrecise(precise);

    }

    /**
     * 【千人计划】创建分组 同时加入分组与用户绑定关系表中
     */
    @Transactional(rollbackFor = Exception.class)
    @PostMapping("/demoPersonnel/createGroup")
    public void createGroupInDemoPersonnel(@RequestBody PersonGroupDTO groupDTO) {
        preciseService.createGroup(groupDTO);
    }


    /**
     * 【千人计划】获取分组列表
     *
     * @return
     */
    @GetMapping("/demoPersonnel/getGroupList")
    public PageInfo<Map<String, Object>> getGroupList(@RequestParam(value = "pageIndex", defaultValue = "1", required = false) int pageIndex,
                                                      @RequestParam(value = "pageSize", defaultValue = "10", required = false) int pageSize) {
        PageHelper.startPage(pageIndex, pageSize);
        return new PageInfo<>(preciseService.getGroupList());
    }


    /**
     * 【千人计划】获取人员列表 带筛选条件
     * email 邮件
     * domain 标签
     * city 地区
     * name 名字
     *
     * @return
     */
    @GetMapping("/demoPersonnel/getAuthList")
    public PageInfo<Map<String, Object>> getAuthList(
            @RequestParam(value = "pageIndex", defaultValue = "1", required = false) int pageIndex,
            @RequestParam(value = "pageSize", defaultValue = "10", required = false) int pageSize,
            @RequestParam(value = "email", required = false) String email,
            @RequestParam(value = "domain", required = false) String domain,
            @RequestParam(value = "name",  required = false) String name,
            @RequestParam(value = "mechanism", required = false) String mechanism,
            @RequestParam(value = "groupId", required = false) String groupId,
            @RequestParam(value = "city", required = false) String city) {

        List<String> idsListByGroupIds = new ArrayList<>();

        if (groupId != null && !StringUtils.isEmpty(groupId)){

            List<String> GroupIdList = CreateListStrUtil.build(groupId);
            //根据分组查询用户的author_id(去重)
            idsListByGroupIds = preciseService.getIdsListByGroupIds(GroupIdList);
        }

        //人员筛选条件
        HashMap<String, Object> searchWrapperMap = new HashMap<>();
        searchWrapperMap.put(Constants.AuthorWrapper.EMAIL, email);
        searchWrapperMap.put(Constants.AuthorWrapper.DOMAIN, domain);
        searchWrapperMap.put(Constants.AuthorWrapper.CITY, city);
        searchWrapperMap.put(Constants.AuthorWrapper.NAME, name);
        searchWrapperMap.put(Constants.AuthorWrapper.MECHANISM, mechanism);
        searchWrapperMap.put(Constants.AuthorWrapper.AUTHOR_IDS, idsListByGroupIds);

        PageHelper.startPage(pageIndex, pageSize);
        return new PageInfo<>(preciseService.getAuthList(searchWrapperMap));
    }


    /**
     * 【千人计划】 服务层 根据分组查找人员EmailList
     * 【为了一会测试使用 才开放接口】
     * 分组关系表 -> 绑定关系的人员ids todo 多个分组 去重发送
     * ids-> emails
     *
     * @return
     */
    @GetMapping("/demoPersonnel/queryDemoEmailsListByGroupId")
    public List<String> queryDemoListByGroup(@RequestParam(value = "groupId") String groupId) {
        return preciseService.getAuthorEmailsListByGroupId(groupId);
    }

    /**
     * 【千人计划】 创建任务列表中
     */
    @PostMapping("/demoPersonnel/addPreciseToDemoTask")
    public void addDemoTask(HttpServletRequest request, @RequestBody AuthorTask authorTask) throws ExecutionException, InterruptedException {
        preciseService.addPreciseToDemoTask(authorTask, request);
    }

    /**
     * 【千人计划】获取任务列表
     */
    @GetMapping("/demoPersonnel/getDemoTaskList")
    public PageInfo<AuthorTask> getDemoTaskList(
            @RequestParam(value = "pageIndex", defaultValue = "1", required = false) int pageIndex,
            @RequestParam(value = "pageSize", defaultValue = "10", required = false) int pageSize) {
        PageHelper.startPage(pageIndex, pageSize);
        return new PageInfo<>(preciseService.getTaskList());
    }


    /**
     * 【千人计划】根据taskId 获取数据统计
     * allSendCount 发送数量 = 人群总人数（去重之后）
     * successCount 发送成功数量
     * wxBindCount  微信绑定数量
     * readListByTask 推送报告
     * readTrend  阅读趋势
     */
    @GetMapping("/demoPersonnel/getPushResultByTaskId")
    public Map<String, Object> getPushResultByTaskId(@RequestParam(value = "taskId", required = true) String taskId) {
        return preciseService.getPushResultByTaskId(taskId);
    }


    /**
     * 【千人计划】获取任务详情
     */
    @GetMapping("/demoPersonnel/getTaskInfo")
    public Map<String, Object> getTaskInfo(@RequestParam(value = "taskId", required = true) String taskId) {
        return preciseService.getTaskInfo(taskId);
    }
}
